package com.eoe.wiki.view;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import android.content.Context;
import android.util.AttributeSet;
import android.view.View;
import android.view.ViewGroup;
import android.view.animation.Animation;
import android.view.animation.Animation.AnimationListener;
import android.view.animation.TranslateAnimation;

import com.eoe.wiki.utils.L;

public class SliderLayer extends ViewGroup {

	protected List<SliderEntity> mListLayers;
	protected Animation mAnimation;
	protected Set<SliderListener> mListeners;

	private int mOpenLayerIndex;
	private boolean isAnimationing = false;
	
	public static final long DURATION = 500;
	
	public SliderLayer(Context context) {
		super(context);
		// TODO Auto-generated constructor stub
		
	}
	
	public SliderLayer(Context context,AttributeSet attrs){
		super(context, attrs);
		mListLayers = new ArrayList<SliderEntity>();
		mListeners = new HashSet<SliderLayer.SliderListener>();
	}

	public void addLayer(SliderEntity layer){
		if(layer==null){
			throw new NullPointerException(" can't add a null layer");
		}
		mListLayers.add(layer);
	}
	
	public int getLayerCount(){
		return mListeners.size();
	}
	
	public ViewGroup getCurrentOpengingLayer(){
		return getLayer(mOpenLayerIndex);
	}
	
	public ViewGroup getLayer(int index){
		int count = mListLayers.size();
		if(index>count||index<0){
			throw new IllegalArgumentException("Invalid layer index. 0<=idnex<=" + count);
		}
		return mListLayers.get(index).getView();
	}
	
	@Override
	protected void onLayout(boolean changed, int l, int t, int r, int b) {
		// TODO Auto-generated method stub
		int count = mListLayers.size();
		for(int i=0;i<count;i++){
			SliderEntity layer = mListLayers.get(i);
			if(i<mOpenLayerIndex){
				layer.view.layout(layer.openX, layer.y, r, b);
			}else{
				layer.view.layout(layer.closeX, layer.y, r + layer.closeX, b);
			}
		}
	}
	
	public void addSliderListener(SliderListener l){
		L.d("add a slider listener");
		mListeners.add(l);
	}
	
	public void removeSliderListener(SliderListener l){
		if(mListeners.contains(l)){
			mListeners.remove(l);
		}
	}
	
	public int openingLayerIndex(){
		return mOpenLayerIndex;
	}
	
	public boolean isAnimationing(){
		return isAnimationing;
	}

	public void openSidebar(int index){
		if(index <= mOpenLayerIndex){
			L.e("index must greater than the opening layer index");
			return;
		}
		if(index>mListLayers.size()){
			L.e("index must less than the maxlayer index" + mListLayers.size());
			return;
		}
		SliderEntity layer = mListLayers.get(index);
		if(layer.view.getAnimation()!=null){
			return;
		}
		L.d("try to open:" + index);
		mAnimation = new TranslateAnimation(0, -(layer.closeX-layer.openX), 0, 0);
		mAnimation.setAnimationListener(new OpenListener(layer.view));
		
		mAnimation.setDuration(DURATION);
		mAnimation.setFillAfter(true);
		mAnimation.setFillEnabled(true);
		
		mOpenLayerIndex = index;
		layer.view.startAnimation(mAnimation);
	}
	
	public void closeSidebar(int index){
		if(index != mOpenLayerIndex){
			L.e("Can`t close the layer which is not opening");
			return;
		}
		
		SliderEntity layer = mListLayers.get(index);
		if(layer.view.getAnimation()!=null){
			return;
		}
		
		mAnimation = new TranslateAnimation(0, (layer.closeX-layer.openX), 0, 0);
		mAnimation.setAnimationListener(new OpenListener(layer.view));
		
		mAnimation.setDuration(DURATION);
		mAnimation.setFillAfter(true);
		mAnimation.setFillEnabled(true);
		
		mOpenLayerIndex--;
		layer.view.startAnimation(mAnimation);
	}	
	
	class OpenListener implements Animation.AnimationListener{
		View iContent;
		OpenListener(View content){
			this.iContent = content;
		}
		@Override
		public void onAnimationStart(Animation animation) {
			// TODO Auto-generated method stub
			isAnimationing = true;
		}
		@Override
		public void onAnimationEnd(Animation animation) {
			// TODO Auto-generated method stub
			iContent.clearAnimation();
			requestLayout();
			List<SliderListener> result = set2List(mListeners);
			for(SliderListener l :result){
				l.sliderbarOpened();
			}
			isAnimationing =false;
			
			
		}
		@Override
		public void onAnimationRepeat(Animation animation) {
			// TODO Auto-generated method stub
			
		}
		
		
	}
	
	class CloseListener implements Animation.AnimationListener{
		View iContent;
		
		

		public CloseListener(View content) {
			super();
			this.iContent = content;
		}

		@Override
		public void onAnimationStart(Animation animation) {
			// TODO Auto-generated method stub
			isAnimationing = true;
		}

		@Override
		public void onAnimationEnd(Animation animation) {
			// TODO Auto-generated method stub
			
		}

		@Override
		public void onAnimationRepeat(Animation animation) {
			// TODO Auto-generated method stub
			iContent.clearAnimation();
			List<SliderListener> result = set2List(mListeners);
			for(SliderListener l :mListeners){
				l.sliderbarClosed();
			}
			isAnimationing = false;
		}
		
	}
	public List<SliderListener> set2List(Set<SliderListener> sets){
		if(sets==null){
			return null;
		}
		List<SliderListener> result = new ArrayList<SliderLayer.SliderListener>(sets.size());
		for(SliderListener l:mListeners){
			result.add(l);
		}
		return result;
	}
	
	public interface SliderListener{
		public void sliderbarOpened();
		public void sliderbarClosed();
		public boolean contentTouchedWhenOpening();
	}
}
